{
  Copyright 2012 Sergey Ostanin

  Licensed under the Apache License, Version 2.0 (the "License");
  you may not use this file except in compliance with the License.
  You may obtain a copy of the License at

      http://www.apache.org/licenses/LICENSE-2.0

  Unless required by applicable law or agreed to in writing, software
  distributed under the License is distributed on an "AS IS" BASIS,
  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  See the License for the specific language governing permissions and
  limitations under the License.
}

unit TestUtils;

interface

uses
  Classes, SysUtils, TestCore, Pad, Profile, Math, MiscUtils;

const
  TEST_DOCUMENT_MIME_TYPE = 'application/x-irenproject.ru-testDocument';

type
  TQuestionWithFormulation = class(TQuestion)
  private
    FFormulation: TPad;
  protected
    function GetTitle: String; override;
  public
    constructor Create; override;
    destructor Destroy; override;
    procedure Assign(Source: TQuestion); override;
    function ReplaceString(const OldString, NewString: String): Integer; override;

    property Formulation: TPad read FFormulation;
  end;

  TTestDocument = class
  private
    FTest: TTest;
    FProfiles: TProfileList;
  public
    constructor Create;
    destructor Destroy; override;
    function ExtractTest: TTest;
    function ExtractProfiles: TProfileList;

    property Profiles: TProfileList read FProfiles;
    property Test: TTest read FTest;
  end;

function EvaluateMappingDichotomically(const Correct, Candidate: TIntegerArray): Single;
function EvaluateMappingLaxly(const Correct, Candidate: TIntegerArray): Single;

implementation

function EvaluateMappingDichotomically(const Correct, Candidate: TIntegerArray): Single;
var
  i: Integer;
begin
  Assert( Length(Correct) = Length(Candidate) );

  Result := 1;
  for i := 0 to High(Correct) do
    if Correct[i] <> Candidate[i] then
    begin
      Result := 0;
      Break;
    end;
end;

function EvaluateMappingLaxly(const Correct, Candidate: TIntegerArray): Single;
var
  i, n: Integer;
begin
  Assert( Length(Correct) = Length(Candidate) );

  n := 0;
  for i := 0 to High(Correct) do
    if Candidate[i] <> -1 then
      if Candidate[i] = Correct[i] then
        Inc(n)
      else
        Dec(n);

  n := Max(n, 0);
  if n = Length(Correct) then
    Result := 1
  else
    Result := n / Length(Correct);
end;

{ TQuestionWithFormulation }

constructor TQuestionWithFormulation.Create;
begin
  inherited;
  FFormulation := TPad.Create;
end;

destructor TQuestionWithFormulation.Destroy;
begin
  FreeAndNil(FFormulation);
  inherited;
end;

function TQuestionWithFormulation.GetTitle: String;
begin
  Result := UTF8Encode(FFormulation.Text);
end;

function TQuestionWithFormulation.ReplaceString(const OldString, NewString: String): Integer;
begin
  Result := inherited + FFormulation.ReplaceString(OldString, NewString);
end;

procedure TQuestionWithFormulation.Assign(Source: TQuestion);
begin
  inherited;
  FFormulation.Assign((Source as TQuestionWithFormulation).FFormulation);
end;

{ TTestDocument }

constructor TTestDocument.Create;
begin
  inherited;
  FTest := TTest.Create;
  FProfiles := TProfileList.Create;
end;

destructor TTestDocument.Destroy;
begin
  FreeAndNil(FTest);
  FreeAndNil(FProfiles);
  inherited;
end;

function TTestDocument.ExtractProfiles: TProfileList;
begin
  Result := FProfiles;
  FProfiles := nil;
end;

function TTestDocument.ExtractTest: TTest;
begin
  Result := FTest;
  FTest := nil;
end;

end.

